﻿/*
 * MiniFox.Portlet v3.0.0
 * Docs & License: http://hanko12.com
 * (c) 2019 漢口十二
 */

+function (global, factory) {
    if (typeof define === 'function' && define.amd) {
        define(['jquery'], factory);
    }
    else {
        var $ = jQuery || require('jquery');
        if (typeof exports === 'object' && typeof module !== 'undefined') {
            module.exports = factory($);
        }
        else {
            global.MiniFox = global.MiniFox || {};
            global.MiniFox.Portlet = factory($);
        }
    }
}(this, function ($) {
    "use strict";

    var Widget = (function () {
        var container = MiniFox.extend(MiniFox.Container, function () {
            var tmpl = this.dataTemplate;
            $.template(this.name, tmpl);
            var promise = this.dataSource && this.dataSource.url;
            this.task = new MiniFox.Task(this.name, {
                context: this,
                interval: this.schedule.interval,
                delay: this.schedule.delay,
                once: this.schedule.once,
                promise: (promise ? MiniFox.http : null),
                arguments: this.dataSource,
                onAction: function (arg) {
                    if (arg) {
                        var $html = $.tmpl(this.name, arg.data);
                        $('#' + this.name).html($html);
                        if (this.script) {
                            try {
                                var func = new Function('data', this.script);
                                func.apply(this, [arg.data]);
                            } catch (e) {
                                console.log(e);
                            }
                        }
                    }
                },
                onError: function (e) {
                    //$.alert(e);
                }
            });

        });
        container.prototype.init = function () {
            
        };
        container.prototype.mergeOptions = function (option) {
            this._id = option.id;
            var defaults = {
                id: null,
                name: null,
                title: null,
                icon: null,
                colSpan: 4,
                rowSpan: 1,
                className: "",
                enterUrl: null,
                showHeader: false,
                showFooter: false,
                template: "",
                schedule: { delay: 0, once: true, interval: 60000 },
                dataSource: {
                    url: null,
                    method: "get",
                    headers: null,
                    params: null,
                    data: null
                },
                dataTemplate: null,
                editMode: this.$parent.editMode,
                updated: function () {
                    this.layout();
                }
            };
            return $.extend({}, defaults, option);
        };
        container.prototype.domInit = function () {
            this.$element.find(".data-content").css("height", `calc( 100% - ${(this.showHeader ? 26 : 0)}px - ${(this.showFooter ? 25 : 0) }px)`);
            this.$element.delegate("a[data-target='module'][data-url]", "click", function () {

                var agent = new MiniFox.Agent();


                var openMode = $(this).attr("data-open");
                var icon = $(this).attr("data-icon");
                var url = $(this).attr("data-url");
                var title = $(this).prop("title");
                switch (openMode) {
                    case "1":
                        window.open(url);
                        break;
                    case "2":
                        //对话框
                        break;
                    default:
                        agent.sendMessage("enter", [url, title, icon]);
                        break;
                }
                return false;
            });
            if (this.task && !this.task.running)
                this.task.start();
            
        };
        container.prototype.layout = function () {
            this.$element.find(".data-content").css("height", `calc( 100% - ${(this.showHeader ? 26 : 0)}px - ${(this.showFooter ? 25 : 0)}px)`);

            this.$element.delegate(".tool .remove[data-target='" + this.id + "']", "click", this.$options, (function (widget) {
                return function (e) {
                    widget.$parent.removeWidget(e.data);
                }
            })(this));
            if (this.task)
                this.task.restart();
        };

        return container;
    })();

    var Portlet = (function () {
        var container = MiniFox.extend(MiniFox.Container, function () {
            +function (portlet) {
                var hasUpdated = false;
                Object.defineProperty(portlet, "hasUpdated", {
                    configurable: false,
                    enumerable: false,
                    get: function () {
                        return hasUpdated;
                    },
                    set: function (newVal) {
                        if (hasUpdated !== newVal) {
                            hasUpdated = newVal;
                            portlet.editing(newVal);
                        }
                    }
                });

            }(this);
        });
        container.prototype.init = function () {
            var change = function () {
                for (var name in this.components) {
                    var widget = this.components[name];
                    widget.editMode = this.editMode;
                }
            };
            this.watcher = {
                editMode: {
                    onchange: change
                }
            };
        };
        container.prototype.mergeOptions = function (option) {
            var defaults = {
                editMode: false,
                widgets: [],
            }
            return $.extend({}, defaults, option);
        };
        container.prototype.createComponents = function () {

            this.loadWidgets();
        };
        container.prototype.loadWidgets = function () {

            +function (portlet) {

                if (portlet.widgets && portlet.widgets.length > 0) {
                    portlet.widgets.forEach(function (item) {
                        portlet.loadWidget(item);
                    });
                }

            }(this);

        };
        container.prototype.loadWidget = function (option) {
            if (!option.name)
                option.name = MiniFox.createGUID();
            var widget = new Widget(option, this);
            this.components[option.name] = widget;
        };
        container.prototype.initDom = function () {

            if ($.isFunction(this.onCreated))
                this.onCreated();
        };
        container.prototype.layout = function () {
            var portlet = this;
            this.$element.sortable({
                connectWith: ".widget",
                handle: ".editMode",
                helper:"clone",
                update: function (event, ui) {

                    var index = $(this).children().index(ui.item)
                    var id = ui.item.attr("data-id");
                    var widgetOption = portlet.widgets.singleOrDefault(function (item) {
                        return item.id == id;
                    });
                    portlet.widgets.remove(widgetOption);
                    portlet.widgets.insert(widgetOption, index);
                    if (portlet.editMode)
                        portlet.hasUpdated = true;
                }
            });
        };
        container.prototype.enterEdit = function () {
            this.editMode = true;
            
        };
        container.prototype.exitEdit = function () {
            this.editMode = false;
            this.hasUpdated = false;
        };
        container.prototype.createWidgets = function (options) {
            if (options) {
                for (var i = 0; i < options.length; i++) {
                    this.createWidget(options[i]);
                }
            }
        }
        container.prototype.createWidget = function (option) {
            if (this.widgets.any(function (w) { return w.id === option.id || w.name === option.name; })) {
                return;
            }
            this.widgets.push(option);
            this.loadWidget(option);

            if ($.isFunction(this.taskAdded))
                this.taskAdded(option);
            if (this.editMode)
                this.hasUpdated = true;
        };
        container.prototype.removeWidget = function (option) {
            var widget = this.components[option.name];
            widget.task.stop();
            widget.$element.remove();
            delete this.components[widget.name];
            this.widgets.remove(function (e) { return e.name === widget.name });

            if ($.isFunction(this.removed))
                this.removed(widget);
            if (this.editMode)
                this.hasUpdated = true;
        };
        container.prototype.clearWidgets = function () {

            for (var i = 0; i < this.widgets.length; i++) {
                var option = this.widgets[i];
                var widget = this.components[option.name];
                widget.task.stop();
                widget.$element.remove();
                delete this.components[widget.name];
            }
            this.widgets = [];
            if (this.editMode)
                this.hasUpdated = false;
        };
        return container;
    })();

    return Portlet;
});